package Sudoku3.solver;
import Sudoku3.io.textEngine;
import Sudoku3.rules.*;
import Sudoku3.structure.*;


public class solver extends Thread {
	
	private grid _g;
	private textEngine _t;


	
	public solver(grid g) {
		_g = g;
		_t = new textEngine(_g);
	}
	
	public boolean isSolved() {
		boolean _solved = true;
		
		for (int r = 0; r < 9; r++) {
			for (int c = 0; c < 9; c++) {
				if (_g.getCell(r, c).getValue() ==0 ) { _solved = false; }
			}
		}
		return _solved;
	}
	
	public void solve() {
		
		
			
			while  (!isSolved())  {
				String state1 = _t.toStringState();
				
				for (int i = 0; i < 9; i++) {
					for (cell c : _g.getRow(i)) {
						rule01_explicit_value rule01 = new rule01_explicit_value(c);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					for (cell c : _g.getRow(i)) {
						rule02_naked_single rule02 = new rule02_naked_single(c);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					for (cell c : _g.getRow(i)) {
						rule03_neighboring_value rule03 = new rule03_neighboring_value(c);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					for (Class <? extends group> grouptype : _g.getGroupTypes()) {
						group grp;
						if (grouptype == row.class) { grp = _g.getRow(i); }
						else if (grouptype == col.class) { grp = _g.getCol(i); }
						else { grp = _g.getBlk(i); }
						
						rule04_hidden_single rule04 = new rule04_hidden_single(grp);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					for (Class <? extends group> grouptype : _g.getGroupTypes()) {
						group grp;
						if (grouptype == row.class) { grp = _g.getRow(i); }
						else if (grouptype == col.class) { grp = _g.getCol(i); }
						else { grp = _g.getBlk(i); }
						
						rule05_naked_set rule05 = new rule05_naked_set(grp);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					for (Class <? extends group> grouptype : _g.getGroupTypes()) {
						group grp;
						if (grouptype == row.class) { grp = _g.getRow(i); }
						else if (grouptype == col.class) { grp = _g.getCol(i); }
						else { grp = _g.getBlk(i); }
						
						rule06_hidden_set rule06 = new rule06_hidden_set(grp);
					}
				}
				
				for (int i = 0; i < 9; i++) {
					try {
						rule07_common_crossing rule07 = new rule07_common_crossing(_g.getBlk(i), _g);
					} catch (Exception e) {
						e.printStackTrace();
					}
				}
				
				
				
	//			//individual cell checks (easiest)
	//			for (int i = 0; i < 9; i++) {
	//				for (cell c : _g.getRow(i)) {
	//					rule01_explicit_value rule01 = new rule01_explicit_value(c);
	//					rule02_naked_single rule02 = new rule02_naked_single(c);
	//					rule03_neighboring_value rule03 = new rule03_neighboring_value(c);
	//				}
	//				
	//				for (Class <? extends group> grouptype : _g.getGroupTypes()) {
	//					group grp;
	//					if (grouptype == row.class) { grp = _g.getRow(i); }
	//					else if (grouptype == col.class) { grp = _g.getCol(i); }
	//					else { grp = _g.getBlk(i); }
	//					
	//					rule04_hidden_single rule04 = new rule04_hidden_single(grp);
	//					rule05_naked_set rule05 = new rule05_naked_set(grp);
	//					rule06_hidden_set rule06 = new rule06_hidden_set(grp);
	//				}
	//				
	//				rule07_common_crossing rule07 = new rule07_common_crossing(_g.getBlk(i), _g);
	//				
	//			}
				
	//			//group checks
	//			
	//			//iterate through the group types
	//			for (Class <? extends group> grouptype : _g.getGroupTypes()) {
	//				//iterate through groupIDs
	//				for (int i = 0; i < 9; i++) {
	//					
	//					group grp;
	//					if (grouptype == row.class) { grp = _g.getRow(i); }
	//					else if (grouptype == col.class) { grp = _g.getCol(i); }
	//					else { grp = _g.getBlk(i); }
	//					
	//					rule04_hidden_single rule04 = new rule04_hidden_single(grp);
	//					rule05_naked_set rule05 = new rule05_naked_set(grp);
	//					rule06_hidden_set rule06 = new rule06_hidden_set(grp);
	//					
	//
	//					
	//				}
	//			}
	//				
	//			for (int i = 0; i < 9; i++) {
	//				//rule07_common_crossing rule07 = new rule07_common_crossing(_g.getBlk(i), _g);
	//			}
				
	
				
				
				
				String state2 = _t.toStringState();
				
				if (isSolved()) { System.out.println("Solved!"); break; }
				//no change!
				if (state1.equals(state2)) { System.out.println("Stumped!"); break; }
				
			}
			
			validator v = new validator(_g);
			if (isSolved()) {
				if (v.isValid()) { System.out.println("Valid!"); }
				else { System.out.println("Invalid!"); }
			};
			
		}
		
		

	

}
